package cn.tedu._02notice.controller;

import cn.tedu._02notice.base.response.JsonResult;
import cn.tedu._02notice.base.response.StatusCode;
import cn.tedu._02notice.mapper.NoticeMapper;
import cn.tedu._02notice.pojo.dto.NoticeAddDetail;
import cn.tedu._02notice.pojo.dto.NoticeAddParam;
import cn.tedu._02notice.pojo.dto.NoticeAddQuery;
import cn.tedu._02notice.pojo.dto.NoticeUpdateParam;
import cn.tedu._02notice.pojo.entity.Notice;
import cn.tedu._02notice.pojo.vo.Detail;
import cn.tedu._02notice.pojo.vo.NoticeListVO;
import com.github.xiaoymin.knife4j.annotations.ApiOperationSupport;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.Parameter;
import io.swagger.v3.oas.annotations.Parameters;
import io.swagger.v3.oas.annotations.tags.Tag;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.*;

import java.util.Date;
import java.util.List;

/**
 * 功能设计步骤：
 * 1.DTO或VO或ENTITY类
 * 2.Controller
 * 3.Mapper
 * 4.xml配置SQL语句
 * 5.重启项目
 */

/**
 * @RestController注解
 * 1.组合注解
 * 2.类上添加该注解后，所有控制器的方法无需再添加 @Controller 和 @ResponseBody 注解
 *
 * @RequestMapping注解：
 * 该注解不限定请求方式
 *
 * @Slf4j注解：
 * 作用：自动为类添加日志对象log
 * 使用log.xx替换System.out.println
 */
@Tag(name = "01-资讯管理模块")
@Slf4j
@RestController
@RequestMapping("/v1/notice/")
public class NoticeController {
    @Autowired
    private NoticeMapper noticeMapper;

    /**
     * 1.添加资讯功能
     */
    @PostMapping("add")
    //  1.@Tag(name="xxx"): 该注解用于描述接口的分组，在 Knife4j 中显示为接口的分组。
    //  2.@Operation(summary = "xxx"):  该注解用于描述接口的功能，在 Knife4j 中显示为接口的标题。
    //  3.@ApiOperationSupport(order = xx): 该注解用于设置接口的顺序，数字越小越靠前。
    //  4.@Parameters(value = {xxx}): 该注解用于描述接口的参数，在 Knife4j 中显示为接口的参数。
    //  5.Schema()
    @Operation(summary = "1.添加资讯")
    @ApiOperationSupport(order = 10)
    @Parameters(value = {
            @Parameter(name = "title",description = "资讯标题"),
            @Parameter(name = "content",description = "资讯内容"),
            @Parameter(name = "type",description = "资讯类型"),
            @Parameter(name = "status",description = "资讯状态"),
            @Parameter(name = "noticeAddParam",hidden = true)
    })
    public JsonResult add(NoticeAddParam noticeAddParam) {
        log.debug("noticeAddParam="+noticeAddParam);
        //1.将资讯信息添加到数据库的notice表中
        Notice notice = new Notice();
//        notice.setTitle(noticeAddParam.getTitle());
//        notice.setContent(noticeAddParam.getContent());
//        notice.setType(noticeAddParam.getType());
//        notice.setStatus(noticeAddParam.getStatus());

        //作用是将 noticeAddParam 对象中的属性值复制到 notice 对象中，简化属性赋值操作。
        //即：自动把 title、content、type、status 四个字段从 NoticeAddParam 拷贝到 Notice 对象中。
        BeanUtils.copyProperties(noticeAddParam, notice);
        notice.setUserId(1L);
        notice.setUpdateTime(new Date());
        notice.setCreateTime(new Date());

        noticeMapper.insertNotice(notice);
        return JsonResult.ok();
    }

    /**
     *2.添加资讯列表功能
     */
    @GetMapping("list")
    @Operation(summary = "2.资讯列表")
    @ApiOperationSupport(order = 20)
    public JsonResult list(NoticeAddQuery noticeAddQuery) {
        log.debug("noticeAddQuery=" + noticeAddQuery);
        List<NoticeListVO> noticeListVOList = noticeMapper.selectNoticeList(noticeAddQuery);
        return JsonResult.ok(noticeListVOList);
    }

    /**
     * 3.添加资讯详情功能
     */
    @GetMapping("detail")
    @Operation(summary = "3.资讯详情")
    @ApiOperationSupport(order = 30)
    @Parameters(value = {
            @Parameter(name = "title",description = "资讯标题",required = true,example = "我是标题"),
            //hidden = true 表示该参数不会在接口文档中显示
            @Parameter(name = "username",description = "用户名",required = true,hidden = true)})
    public JsonResult detail(NoticeAddDetail noticeAddDetail) {
        log.debug("noticeAddDetail=" +  noticeAddDetail);
        Detail detail = noticeMapper.selectNoticeDetail(noticeAddDetail.getId());
        return JsonResult.ok(detail);
    }

    /**
     * 4.删除资讯功能
     */
    @DeleteMapping("del")
    @Operation(summary = "4.删除资讯")
    @ApiOperationSupport(order = 40)
    public JsonResult del(Long id){
        log.debug("id="+id);
        int num = noticeMapper.deleteNotice(id);
        if (num>0){
            return JsonResult.ok();
        }else {
            return new JsonResult(StatusCode.OPERATION_FAILED);
        }
    }

    /**
     * 5.更新资讯功能
     */
    @PostMapping("update")
    @Operation(summary = "5.更新资讯")
    @ApiOperationSupport(order = 50)
    public JsonResult update(NoticeUpdateParam noticeUpdateParam){
        log.debug("noticeUpdateParam="+ noticeUpdateParam);
        Notice notice = new Notice();
        BeanUtils.copyProperties(noticeUpdateParam, notice);
        notice.setUpdateTime(new Date());
        int num = noticeMapper.updateNotice(notice);
        if(num >  0){
            return JsonResult.ok();
        }
        return new JsonResult(StatusCode.OPERATION_FAILED);
    }
}
